package be.groept.ace.cursusplanning.utils;

import java.util.Calendar;

import be.groept.ace.cursusplanning.model.LesDag;
import be.groept.ace.cursusplanning.persistency.IPersistentieController;
import be.groept.ace.cursusplanning.persistency.IPersistentieProvider;
import be.groept.ace.cursusplanning.persistency.Persisteerbaar;

public class TijdsMoment1Dag implements Comparable<TijdsMoment1Dag>, Persisteerbaar{
	
	private Calendar begintijd;
	private Calendar eindtijd;
	private int duurtijd = 0;
	private LesDag dag;
	
	private IPersistentieProvider pProvider;

	
	//EXTRA UIT TE WERKEN OF NA TE KIJKEN
	public int getDuurInMinuten(){
		return duurtijd;
	}
	//EXTRA UIT TE WERKEN OF NA TE KIJKEN
	public LesDag getDag(){
		return dag;
	}
	
	public TijdsMoment1Dag(LesDag dag, Integer startuur, Integer startminuten, Integer duurtijd) throws IllegalArgumentException{
		
		setBegintijd(dag, startuur, startminuten);
		setEindtijd(duurtijd);
		this.dag = dag;
	}
	
	private void setBegintijd(LesDag dag, int startuur, int startminuten) throws IllegalArgumentException{
		begintijd = Calendar.getInstance(); 
		
		if(startuur < begintijd.getActualMinimum(Calendar.HOUR_OF_DAY) || startuur > begintijd.getActualMaximum(Calendar.HOUR_OF_DAY)) throw new IllegalArgumentException("Uren moeten tussen 0 en 23 zijn");
		if(startminuten < begintijd.getActualMinimum(Calendar.MINUTE) || startminuten > begintijd.getActualMaximum(Calendar.MINUTE)) throw new IllegalArgumentException("Minuten moeten tussen 0 en 59 zijn");
		if(dag == null) throw new IllegalArgumentException("Lesdag mag niet null zijn.");
		
		begintijd.add(Calendar.DAY_OF_WEEK, dag.getCalendarDag() - Calendar.DAY_OF_WEEK);
		begintijd.set(1, 1, 1, startuur, startminuten);
		
	}
	
	public Calendar getBegintijd() {
		return begintijd;
	}
	
	private void setEindtijd(int duurtijd) throws IllegalArgumentException{
		if(duurtijd <= 0) throw new IllegalArgumentException("Duurtijd kan niet negatief of 0 zijn.");
		eindtijd = (Calendar)begintijd.clone();
		eindtijd.add(Calendar.MINUTE, duurtijd);
		if (begintijd.get(Calendar.DAY_OF_WEEK) < eindtijd.get(Calendar.DAY_OF_WEEK)) throw new IllegalArgumentException("Duurtijd mag niet tot de volgende dag duren.");
		this.duurtijd = duurtijd;
	}
	
	public Calendar getEindtijd() {
		return eindtijd;
	}
	
	/**
	 * Comparen op begintijd
	 */
	@Override
	public int compareTo(TijdsMoment1Dag tijdsmoment1Dag) {
		return getBegintijd().compareTo(tijdsmoment1Dag.getBegintijd());
	}
	
	@Override
	public String toString() {
		return String.format("Start: %1$tA, om %1$tH:%1$tM Einde: %2$tA, om %2$tH:%2$tM", getBegintijd(), getEindtijd());
	}
	
	public boolean overlapt(TijdsMoment1Dag andereMoment) {
		if (this.compareTo(andereMoment) <= 0) {
			if (this.getEindtijd().compareTo(andereMoment.getBegintijd()) <= 0 ) return false;
			return true;
		}
		if (this.getBegintijd().compareTo(andereMoment.getEindtijd()) >= 0) return false;
		return true;
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result
				+ ((begintijd == null) ? 0 : begintijd.hashCode());
		result = prime * result
				+ ((eindtijd == null) ? 0 : eindtijd.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		TijdsMoment1Dag other = (TijdsMoment1Dag) obj;
		if (begintijd == null) {
			if (other.begintijd != null)
				return false;
		} else if (!begintijd.equals(other.begintijd))
			return false;
		if (eindtijd == null) {
			if (other.eindtijd != null)
				return false;
		} else if (!eindtijd.equals(other.eindtijd))
			return false;
		return true;
	}

	@Override
	public Object[] getInfoToBeSaved(IPersistentieController pController) {
		return pProvider.getInfoToBeSaved(pController);

	}
	public IPersistentieProvider getPersistentieProvider(){
		return pProvider;
	}
	public void setPersistentieProvider(IPersistentieProvider provider){
		this.pProvider = provider;
	}

}